package com.qianduo.filter;

import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

import org.dom4j.Document;
import org.dom4j.Element;
import org.dom4j.io.SAXReader;

import com.qianduo.util.Constants;
import com.qianduo.util.Global;
import com.qianduo.vo.AccountForm;
import com.qianduo.vo.RoleURL;

import common.util.EncodeUtil;
import common.util.ListUtil;
import common.util.ObjectUtil;

public class EncodeFilter implements Filter {
	private String encoding;
	
	public void destroy() {
	}
	public boolean roleFilter(Integer access,String path,String queryString){
		boolean retBool				= false;
		List<RoleURL> listRoleURL	= Global.roleMap.get(access);
		if(!ListUtil.isEmpty(listRoleURL)){
			for(RoleURL ru:listRoleURL){
				String tmpPath		= ru.getPath();
				String tmpAction	= ru.getAction();
				if(path.equals(tmpPath) && queryString.indexOf("action="+tmpAction) > -1){
					retBool			= true;
				}
			}
		}else{
			retBool=true;
		}		
		return retBool;
	}
	public void validateSession(HttpServletRequest req,HttpServletResponse res, FilterChain fc) throws IOException,ServletException{
		String requestURI 	= req.getRequestURI();
		String contextPath 	= req.getContextPath();
		requestURI 			= requestURI.substring(contextPath.length());
		String queryString	= req.getQueryString();		
		HttpSession session = req.getSession(false);
		if ( "/".equals(requestURI) ||
			 "/index.jsp".equals(requestURI) 			|| 
			 requestURI.startsWith("/style") 			||
			 requestURI.startsWith("/images") 			||
			 requestURI.startsWith("/scripts") 			||
			 requestURI.startsWith("/imageServlet")		||
			 requestURI.startsWith("/login.do") 		||
			 requestURI.startsWith("/pages")
			 ) {
			fc.doFilter(req, res);
		} else {
			if (ObjectUtil.isEmpty(session)) {
				session 	= req.getSession(true);
				res.sendRedirect(contextPath + "/");
			} else {
				Object accountObj		= session.getAttribute(Constants.ACCOUNT);
				if (ObjectUtil.isEmpty(accountObj)) {
					res.sendRedirect(contextPath + "/");
				} else {
					AccountForm account	= (AccountForm)accountObj;
					if("/TTTTTT.do".equals(requestURI) ){
						String path		= requestURI.substring(1);
						if(roleFilter(account.getType(),path,queryString)){
							fc.doFilter(req, res);
						}else{
							res.sendRedirect(contextPath + "/pages/jsp/accessDenied.jsp");
						}
					}else{
						fc.doFilter(req, res);
					}
				}
			}
		}
	}
	
	public void doFilter(ServletRequest sreq, ServletResponse sres, FilterChain fc){
		try{
			if(null != encoding && !"".equals(encoding)){
				sreq.setCharacterEncoding(encoding);
				sres.setCharacterEncoding(encoding);
			}
			//fc.doFilter(sreq, sres);
			HttpServletRequest req	= (HttpServletRequest)sreq;
			HttpServletResponse res	= (HttpServletResponse)sres;
			validateSession(req,res,fc);
		}catch(Exception e){
			Constants.log.error("EncodeFilter doFilter",e);
		}
	}
	
	public void init(FilterConfig fc) throws ServletException {
		String ec		= fc.getInitParameter("encoding");
		encoding		= ec;
	}
	
	@SuppressWarnings({"unchecked" })
	public void initRoleMap(){
		Map<Integer,List<RoleURL>> roleMap	= new HashMap<Integer,List<RoleURL>>();
		try{
			String filePath					= EncodeUtil.decodeUTF8(EncodeFilter.class.getClassLoader().getResource("").getPath());
			filePath						= new StringBuilder().append(filePath).append("role.xml").toString();
			SAXReader rd			= new SAXReader();
			Document doc			= rd.read(filePath);
			Element root			= doc.getRootElement();
			List<Element> roleList	= root.elements("Role");
			for(Element roleE:roleList){
				String access		= roleE.attributeValue("access");
				Integer accessInt	= Integer.valueOf(access);
				List<Element> urlList=roleE.elements("URL");
				for(Element urlE:urlList){
					String path		= urlE.attributeValue("path");
					String action	= urlE.attributeValue("action");
					
					RoleURL ru		= new RoleURL();
					ru.setPath(path);
					ru.setAction(action);
					
					List<RoleURL> roleURLList=roleMap.get(accessInt);
					if(ListUtil.isEmpty(roleURLList)){
						roleURLList= new ArrayList<RoleURL>();
						roleURLList.add(ru);
						roleMap.put(accessInt, roleURLList);
					}else{
						roleURLList.add(ru);
					}
				}
			}
		}catch(Exception e){
			Constants.log.error(" EncodeFilter initRoleMap",e);
		}finally{
			Global.roleMap	= roleMap;
		}
	}
}
